home *** CD-ROM | disk | FTP | other *** search
/ The Fatted Calf / The Fatted Calf.iso / Applications / Communication / NewsBase / Source / ITreeBrowser.m < prev    next >
Text File  |  1993-01-12  |  7KB  |  292 lines

  1. /*$Copyright:
  2.  * Copyright (C) 1992.5.22. Recruit Co.,Ltd. 
  3.  * Institute for Supercomputing Research
  4.  * All rights reserved.
  5.  * NewsBase  by ISR, Kazuto MIYAI, Gary ARAKAKI, Katsunori SUZUKI, Kok-meng Lue
  6.  *
  7.  * You may freely copy, distribute and reuse the code in this program under 
  8.  * following conditions.
  9.  * - to include this notice in the source code, if it is to be distributed 
  10.  *   with source code.
  11.  * - to add the file named "COPYING" within the code, which shall include 
  12.  *   GNU GENERAL PUBLIC LICENSE(*).
  13.  * - to display an acknowledgement in binary code as follows: "This product
  14.  *   includes software developed by Recruit Co.,Ltd., ISR."
  15.  * - to display a notice which shall state that the users may freely copy,
  16.  *   distribute and reuse the code in this program under GNU GENERAL PUBLIC
  17.  *   LICENSE(*)
  18.  * - to indicate the way to access the copy of GNU GENERAL PUBLIC LICENSE(*)
  19.  *
  20.  *   (*)GNU GENERAL PUBLIC LICENSE is stored in the file named COPYING
  21.  * 
  22.  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
  23.  * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
  24.  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
  25. $*/
  26.  
  27. #import <appkit/Application.h>
  28. #import <appkit/NXBrowser.h>
  29. #import <appkit/Matrix.h>
  30. #import <appkit/graphics.h>
  31. #import <objc/List.h>
  32. #import <mach/mach.h>
  33. #import <string.h>
  34.  
  35. #import "ITreeBrowser.h"
  36. #import "INXBrowserCellWithLinkedObject.h"
  37. #import "IOrderedListD.h"
  38. #import "InfoD.h"
  39. #import "ITreeNodeD.h"
  40. #import "IUifNode.h"
  41. #import "ITreeBrowserMatrix.h"
  42. #import "INewsGroupTreeControl.h"
  43. #import "errdebug.h"
  44.  
  45. @implementation ITreeBrowser
  46.  
  47. - initFrame:(NXRect *)frameRect
  48. {
  49.     [super initFrame:frameRect];
  50.     iAuxAgent = NULL;
  51.     iAuxAction = NULL;
  52.     [self setDelegate:self];
  53.     [self setCellClass:[INXBrowserCellWithLinkedObject class]];
  54.     [self setMatrixClass:[ITreeBrowserMatrix class]];
  55.     
  56.     [self setMultipleSelectionEnabled:YES];
  57.     [self setBranchSelectionEnabled:NO];
  58.     [self setTarget:self];
  59.     [self setAction:@selector(leafPreHandler:)];
  60.     [self useScrollBars:YES];
  61.     [self useScrollButtons:YES];
  62.     [self setPathSeparator:'.'];
  63.     iRootListnode = nil;
  64.  
  65.     return self;
  66. }
  67.  
  68. - (void)setIOmodule:io_module
  69. {
  70.     iIOmodule = io_module;
  71. }
  72.  
  73. - iOmodule
  74. {
  75.     return iIOmodule;
  76. }
  77.  
  78. - (void)setDataGroupUIF:uif_module
  79. {
  80.     iDataGroupUIF = uif_module;
  81. }
  82.  
  83. - (void)setItemRepUIF:uif_module
  84. {
  85.     iItemRepUIF = uif_module;
  86. }
  87.  
  88. - (void)setItemUIF:uif_module
  89. {
  90.     iItemUIF = uif_module;
  91. }
  92.  
  93. - setRootListnode:node
  94. {
  95.     if (iRootListnode != nil ) {
  96.     [iRootListnode free];
  97.     }
  98.  
  99.     iRootListnode = node;
  100.     return self;
  101. }
  102.  
  103. // browser is made of cells(INXBrowserCellWithLinkedObject), and each
  104. // cell has relation to a node(IUifNode) and listnode(IOrderedListD)
  105. //     +---------------------------+
  106. //     | selectedCell --> node     |  +---------------+
  107. //     |               +> listnode +--| cell --> node |
  108. //     +---------------------------+  +---------------+
  109. //                                    | cell --> node |
  110. //                           +---------------+
  111. //                             :
  112. //                    :
  113.  
  114. - (int)browser:sender fillMatrix:matrix inColumn:(int)column
  115. {
  116.     id        selectedCell;
  117.     id        node;
  118.     id        bcell;
  119.     int        row;
  120.     int        i;
  121.     id         child_node;
  122.     id        listnode;
  123.     
  124.     /* for loading column-0, listnode is root node */
  125.     if (column == 0) {
  126.     if((listnode = iRootListnode) == nil) {
  127.     /* initialize without column */
  128.         return 0;
  129.     }
  130.     if ([listnode count] == 0) {
  131.         /* some code for setting title for empty cell should be here */
  132.     }
  133.     } else {
  134.     /* find selection in previous column */
  135.         selectedCell = [[sender matrixInColumn:(column - 1)] selectedCell];
  136.     if ((listnode=[selectedCell listnode]) != nil) {
  137.         [listnode free];
  138.         [selectedCell setListnode:nil];
  139.     }
  140.  
  141.     // if control key is down, do 'toggleActive' under this tree
  142.     if ((int)[[self matrixInColumn:[self lastColumn]] flagsOfLastEvent] 
  143.                                 & NX_CONTROLMASK) {
  144.         [[self matrixInColumn:[self lastColumn]] resetFlagsOfLastEvent];
  145.         [self toggleHandler:selectedCell];
  146.         [[self matrixInColumn:[self lastColumn]] display];
  147.     }
  148.  
  149.     node = [selectedCell node];    
  150.     listnode = [self directoryHandler:node];
  151.     [selectedCell setListnode:listnode];
  152.     }
  153.     
  154.     for (i = 0, row = 0; child_node = [listnode objectAt:i]; ++i) {
  155.     [matrix addRow];
  156.     bcell = [matrix cellAt:row :0];
  157.     [self loadCell:bcell fromNode:child_node];
  158.     [bcell setLoaded:YES];
  159.     ++row;
  160.     /* link this NXBrowserCell with the childNode */
  161.     [bcell setNode:child_node];
  162.  
  163.     /* bcell is leaf or directory */
  164.     if ([child_node isLeaf]) {
  165.         [bcell setLeaf:YES];
  166.     } else {
  167.         [bcell setLeaf:NO];
  168.     }
  169.     /* set cell active or not */
  170.     [bcell setActive:[child_node active]];
  171.     }
  172.     return row;
  173. }
  174.  
  175. - (void)loadCell:bcell fromNode:childNode
  176. {
  177.     id        image;
  178.     
  179.     [bcell setStringValue:(char *)[childNode titleForCell]];
  180.     
  181.     if ((image = [childNode imageForCell]) != nil) {
  182.     [bcell setImage:image];
  183.     }
  184.     return;
  185. }
  186.  
  187. // leafPreHandler will be called when
  188. //   1. clicked directory and also
  189. //   2. clicked leaf
  190. //   3. clicked newsfolder in folder dock matrix 
  191. // this routine will handle
  192. //   - control key & click  -> unsubscribe newsgroup
  193. //   - display folder icon
  194. //   - call leafHandler, which will fill article subject in article's Browser
  195. //
  196. - (void)leafPreHandler:sender
  197. {
  198.     id        lastColumnMatrix, bcellList, bcell;
  199.     int        i, hiliCellCount;
  200.  
  201.     lastColumnMatrix = [self matrixInColumn:[self lastColumn]];
  202.     if ((int)[lastColumnMatrix flagsOfLastEvent] & NX_CONTROLMASK) {
  203.     DBG(1,fprintf(stderr,"-- control key is down"));
  204.     [lastColumnMatrix resetFlagsOfLastEvent];
  205.     [self togglePreHandler:sender];
  206.     return;
  207.     }
  208.     
  209.     // if iTreeBrowser has aux agent, do iAxuAction.
  210.     // now this is used for displaying newsgroup folder icon
  211.     if (iAuxAgent != nil) {
  212.     [iAuxAgent perform:(SEL)iAuxAction with:self];
  213.     }
  214.     
  215.     bcellList = [lastColumnMatrix cellList];
  216.     hiliCellCount=0;
  217.     for (i=0; bcell=[bcellList objectAt:i]; ++i) {
  218.     if ([bcell isHighlighted]) {
  219.         ++hiliCellCount;
  220.     }
  221.     }
  222.     if (hiliCellCount > 1) {
  223.     return;
  224.     } else {
  225.     [self leafHandler:sender];
  226.     }
  227.     return;
  228. }
  229.  
  230. - (void)leafHandler:sender
  231. {
  232.     return;
  233. }
  234.  
  235. - (void)togglePreHandler:sender
  236. {
  237.     id        lastColumnMatrix;
  238.     
  239.     lastColumnMatrix = [self matrixInColumn:[self lastColumn]];
  240.     [lastColumnMatrix sendAction:@selector(toggleHandler:) to:self 
  241.                                 forAllCells:NO];
  242.     /* display matrix after sending toggleActive to cell */
  243.     [lastColumnMatrix display];
  244.     return;
  245. }
  246.  
  247. - (void)toggleHandler:senderCell
  248. {
  249.     id        node;
  250.     
  251.     node = [senderCell node];
  252.     if([iIOmodule toggleActive:node]) {
  253.     /* return YES, if iIOmodule has toggleActive method */
  254.     [senderCell toggleActive];
  255.     if([node active]==YES) {
  256.         [node setActive:NO];
  257.     } else {
  258.         [node setActive:YES];
  259.     }
  260.     }
  261.     return;
  262. }
  263.  
  264. - directoryHandler:node
  265. {
  266.     return [iIOmodule subDirectoryOf:node];
  267. }
  268.  
  269. - setAuxAgent:auxAgent
  270. {
  271.     iAuxAgent = auxAgent;
  272.     return self;
  273. }
  274.  
  275. - auxAgent
  276. {
  277.     return iAuxAgent;
  278. }
  279.  
  280. - setAuxAction:(SEL)auxAction
  281. {
  282.     iAuxAction = auxAction;
  283.     return self;
  284. }
  285.  
  286. - (SEL)auxAction
  287. {
  288.     return iAuxAction;
  289. }
  290.  
  291. @end
  292.